<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<html>
<head>
	<title>notes</title>
	<style type="text/css">
	  table
	  {
	  border-collapse: collapse;
	  }
	  table, tr, th, td
	  {
	  border: 1px solid black;
	  padding-left: 8px;
	  padding-right: 8px;
	  }
	  th, td
	  {
	  min-width: 2em;
	  }
	  pre
	  {
	  border-style: solid
	  }
	  .comment
	  {
	  color: green;
	  }
	</style>
	<link rel="stylesheet" title="plain" type="text/css" href="plain.css" />
	<link rel="alternate stylesheet" title="colour" type="text/css" href="colour.css"/>
</head>
<body>
	<h2>Notes</h2>
	<p>Plan for this class:<ol>
		<li>Review of code so far:<ul>
		    <li>recap</li>
		    <li>what was difficult?</li>
		    <li>deeper, complicated structures</li>
		    <li>repeated blocks</li>
		    <li>data driven exceptions to the rules</li>
		</ul></li>
		<li>The stack:<ul>
		    <li>an array of memory</li>
		    <li>pointer to the top</li>
		    <li>useful for:<ul>
			<li>managing local variables</li>
			<li>maintaining the program state</li>
			<li>temporary workspace</li>
		    </ul></li>
		    <li>you don't get direct access to the stack in C++</li>
		    <li>in assembler:</li>
		    <pre>

     ; assuming eax holds attacker and ebx holds defender
     push eax       ; copy attacker to the top of the stack
     mov eax, ebx   ; copy defender to attacker
     pop ebx        ; copy the top of the stack to defender
		    </pre>

		    <li>how it works (emulated in C++):</li>
		    <pre>

     int stack[100];
     int top = 0;

     ...

     stack[top++] = attacker;
     attacker = defender;
     defender = stack[--top];
		    </pre>
		    <li>top++ means:<ul>
			<li>post-increment: evaluate first, then increment</li>
		    </ul></li>
		    <li>--top means:<ul>
			<li>pre-decrement: decrement first, then evaluate</li>
		    </ul></li>

		</ul></li>
		<li>The subroutine<ul>
		    <li>also known as:<ul>
			<li>function</li>
			<li>procedure</li>
			<li>method</li>
		    </ul></li>
		    <li>extract common code</li>
		    <li>simplify understanding</li>
		    <li>document intention</li>
		    <pre>

int roll(int sides)
{
     return rand() % sides + 1;
}

     ...
     int attack = roll(20) + attacker->attack_bonus;
		    </pre>
		    <li>how it works:</li>
		    <pre>

     <span class="comment">// you can't actually do this in C++</span>
     push 20;
     push calculate_attack_bonus; 
     goto roll;

calculate_attack_bonus:
     pop result;
     int attack = result + attacker-&gt;attack_bonus;
     ...

roll:
     int return_address;
     int sides;

     pop return_address;
     pop sides;
     int result = rand() % sides + 1;
     push result;
     goto return_address;
		    </pre>
		    <li>a return value is not required</li>
		    <pre>

void buffer_console_input(bool buffer)
{
     HANDLE console = GetStdHandle(STD_INPUT_HANDLE);
     DWORD mode;
     GetConsoleMode(console, &amp;mode);

     if (buffer) {

          SetConsoleMode(console, mode | ENABLE_LINE_INPUT);
          cin &gt;&gt; skipws;

     } else {

          SetConsoleMode(console, mode &amp; ~ENABLE_LINE_INPUT);
          cin &gt;&gt; noskipws;
     }
}
		    </pre>
		    <li>but you can only have 1 return value</li>
		    <li>to return more, return a structure as the return value</li>
		    <li>you can have 0 or more parameters</li>
		    <pre>

void do_attack(character * attacker, character * defender)
{
     if (roll(20) + attacker->attack_bonus &gt; defender-&gt;defences[AC]) {

          defender-&gt;hit_points -= roll(attacker-&gt;damage_dice) + attacker-&gt;damage_bonus;
     }
}
		    </pre>
		    <li>parameters are bound in order</li>
		    <li>you cannot access local variables from the caller:</li>
		    <pre>

void swap(int a, int b)
{
     x = b; // illegal: x is undeclared in this scope
     y = a; // illegal: y is undeclared in this scope
}

int main()
{
     int x = 4;
     int y = 5;
     swap(x, y);
}
		    </pre>
		    <li>however, you can pass pointers</li>
		    <pre>

void swap(int * a, int * b)
{
     int temporary = *a;
     *a = *b;
     *b = temporary;
}

int main()
{
     int x = 4;
     int y = 5;
     swap(&x, &y);
}
		    </pre>
		    <li>can we use this to swap our attacker defender variables</li>
		    <li>yes, but...</li>
		    <pre>

void swap(character ** attacker, character ** defender)
{
     character * temporary = *attacker;
     *attacker = *defender;
     *defender = temporary;
}

     ...
     swap (&attacker, &defender);
		    </pre>
		    <li>alternatively</li>
		    <pre>

void swap(character *& attacker, *& defender)
{
     character * temporary = attacker;
     attacker = defender;
     defender = temporary;
}

     ...
     swap(attacker, defender);
		    </pre> 
		    <li>pure functions use only their own parameters</li>
		    <li>non-pure functions have side effects</li>
		    <li>C++ is not a pure functional language</li>
		    <li>but you can write mostly functional code in C++</li>
		    <li>this is desirable as it reduces coupling</li>
		</ul></li>
		<li>Function design principles:<ul>
		    <li>high cohesion</li>
		    <li>low coupling</li>
		</ul></li>
		<li>Function pointers<ul>
		    <li>you can have a pointer to a function</li>
		    <li>this is not a "first class" object in C++</li>
		    <li>it's just a pointer to the code</li>
		    <li>the syntax is a little odd:</li>
		    <pre>

void player_attack(character * attacker, character * defender);
void monster_attack(character * attacker, character * defender);

void (*function)(character * attacker, character * defender);

     ...
     function = player_attack;
     function(attacker, defender);
     ...
     function = monster_attack;
     function(attacker, defender);
		    </pre>
		    <li>this gives us a method to provide character specific code</li>
		    <pre>

struct character {

     const char * name;
     int attack_bonus;
     int damage_dice;
     int damage_bonus;
     int defences[4];
     void (*attack)(character * attacker, character * defender);
     int hit_points;
};

void player_attack(character * attacker, character * defender);
void monster_attack(character * attacker, character * defender);

     ...
     player.attack = player_attack;
     ...
     dragon.attack = monster_attack;
     ...

     do {

          attacker-&gt;attack(attacker, defender);
          swap(attacker, defender);
     
     } while (attacker-&gt;hit_points &gt; 0 && defender-&gt;hit_points &gt; 0);
		    </pre>
		</ul></li>
	  </ol>
	</p>
</body>
</html>
